package dao.xml.dom;

import java.io.IOException;
import java.io.InputStream;
import java.util.ArrayList;
import java.util.Collections;
import java.util.Date;
import java.util.List;

import javax.xml.parsers.DocumentBuilder;
import javax.xml.parsers.DocumentBuilderFactory;
import javax.xml.parsers.ParserConfigurationException;

import model.Datentraeger;
import model.Film;

import org.w3c.dom.Document;
import org.w3c.dom.Element;
import org.w3c.dom.NamedNodeMap;
import org.w3c.dom.Node;
import org.xml.sax.SAXException;

public class DomSample 
{

  private final DocumentBuilder builder;
  private Document document;

  public DomSample() throws ParserConfigurationException
  {
    DocumentBuilderFactory factory = DocumentBuilderFactory.newInstance();
    factory.setNamespaceAware(false);
    factory.setValidating(false);
    factory.setXIncludeAware(false);
    factory.setIgnoringElementContentWhitespace(true);
    builder = factory.newDocumentBuilder();
  }

  public List<Datentraeger> getDatentraegers(InputStream input) throws SAXException, IOException
  {
    List<Datentraeger> datentraegers = Collections.emptyList();
    document = builder.parse(input);
    Element documentElement = document.getDocumentElement();
    if (documentElement.hasChildNodes()) 
    {
    	datentraegers = new ArrayList<Datentraeger>();
    	Node datentraegerNode = documentElement.getFirstChild();
    	while (datentraegerNode != null)
    	{
    		if (datentraegerNode.getNodeType() == Node.ELEMENT_NODE && "datentraeger".equals(datentraegerNode.getNodeName())) 
    		{
    			Datentraeger datentraeger = createDatentraegerFromNode(datentraegerNode);
	    		if (datentraegerNode.hasChildNodes() && datentraegerNode.getFirstChild().getNextSibling().hasChildNodes()) 
	    		{
	    			Node filmNode = datentraegerNode.getFirstChild().getNextSibling().getFirstChild();
	    			while (filmNode != null)
	    			{
	    				if (filmNode.getNodeType() == Node.ELEMENT_NODE && "film".equals(filmNode.getNodeName()))
	    				{
	    					Film film = createFilmFromNode(filmNode);
	    					datentraeger.addFilm(film);
	    				}
	    				filmNode = filmNode.getNextSibling();
	    			}
	    		}
	    		datentraegers.add(datentraeger);
    		}
    		datentraegerNode = datentraegerNode.getNextSibling();
        }
    }
    return datentraegers;
  }

  private Datentraeger createDatentraegerFromNode(Node datentraegerNode)
  {
    NamedNodeMap attributes = datentraegerNode.getAttributes();
    Node nameAttribute = attributes.getNamedItem("name");
    String name = nameAttribute.getNodeValue();
    Date creationDate = new Date();
    Datentraeger currentDatentraeger = new Datentraeger(name, creationDate);
    return currentDatentraeger;
  }

  private Film createFilmFromNode(Node filmNode) 
  {
    NamedNodeMap attributes = filmNode.getAttributes();
    String name = attributes.getNamedItem("name").getNodeValue();
    String hauptdarsteller = attributes.getNamedItem("hauptdarsteller").getNodeValue();
    String genre = attributes.getNamedItem("genre").getNodeValue();
    String laenge = attributes.getNamedItem("laenge").getNodeValue();
    Film film = new Film(name, hauptdarsteller, genre, Integer.parseInt(laenge));
    return film;
  }
}
